home *** CD-ROM | disk | FTP | other *** search
- /*
- * Yamana's Otomeza Plug-in Tool
- * 3点指定円
- *
- * 1995.08.20
- * 1995.08.26 手ぶれんビ~搭載(^^;)
- *
- */
- #include "otome_pi.h"
- #include "costbl.h"
-
- const char longname[] = "DRAW : 3点指定円";
- int cnfg_max = 2;
- PI_CNFG cnfg[] = {
- {"楕円 正円" , 0, 1, 0, 0 },
- {"線の太さ" , 1, 32, 1, 1 }
- };
-
- #define USE_ENV PI_SET_ENV
- #define USE_TYPE PI_EFFC_POLY
- #include "otome_pi.c"
-
- /* 手ぶれとする値 */
- #define TEBURE 3
-
- /*******************************************************/
-
- POINT Points[3];
-
-
- /* 3点の座標を得る */
- int get_Points()
- {
- int ox,oy,i,j;
-
- if( WORD(g_para) < 3 )
- return ERROR;
-
- memcpy( &Points[0], g_para+2, 2*2 ); /* 第1点 */
-
- /* 手ぶれによって点が接近している場合があるので補正する。*/
- i = 0;
- j = 0;
- while( j<2)
- { do
- { i++;
- ox = WORD( g_para+i*4+2 );
- oy = WORD( g_para+i*4+4 );
-
- }while( abs(ox-Points[j].x)<=TEBURE
- && abs(oy-Points[j].y)<=TEBURE && i<WORD(g_para) );
-
- if( i >= WORD(g_para) ) return ERROR;
- j++;
- Points[j].x = ox;
- Points[j].y = oy;
- }
- return NOERR;
- }
-
- /*******************************************************/
-
- int circle_3Points()
- {
- char tmp[2*2];
-
- EGB_bow( EgbPtr, &Points );
-
- /* 2点目と3点目を入れ替えて再実行するだけ */
- memcpy( tmp, &Points[1].x, 2*2 );
- memcpy( &Points[1].x, &Points[2].x, 2*2 );
- memcpy( &Points[2].x, tmp, 2*2 );
-
- EGB_bow( EgbPtr, &Points );
-
- return NOERR;
- }
-
- /* 128角形を楕円変形し回転させる */
- /* 256角形にしても速度差はほとんどないが、誤差が拡大されてしまう */
- #define EN_P 128
-
- int circle_slant()
- {
- register int x,y;
- int t,ox,oy,step;
- int rx,ry,r,rby;
- int rsin,rcos;
- char *para,*p;
-
- if( (para=(char*)PI_MALLOC( 2+ EN_P*4 ))==NULL )
- return PI_ERROR_NO_MEMORY;
-
- #ifdef DEBUG
- printf("(%d,%d)-(%d,%d)-(%d,%d)",
- Points[0].x,Points[0].y,
- Points[1].x,Points[1].y,
- Points[2].x,Points[2].y );
- #endif
-
- /* 最初の2点間の距離÷2を楕円の1つ目の軸長とする */
- x = (Points[0].x - Points[1].x);
- y = (Points[0].y - Points[1].y);
- rx = sqrt( x*x + y*y )/2;
-
- /* 中心点 */
- ox = (Points[0].x + Points[1].x)/ 2 ;
- oy = (Points[0].y + Points[1].y)/ 2 ;
-
- /* 中点と3点目の距離を楕円の2つ目の軸長とする */
- x = (Points[2].x - ox);
- y = (Points[2].y - oy);
- ry = sqrt( x*x + y*y );
-
- rby = 256*ry/rx;
-
- /* 回転角 */
- rsin = ((oy - Points[1].y)<<8 )/ ry;
- rcos = ((ox - Points[1].x)<<8 )/ ry;
- r = ry;
-
- step = 256 / EN_P;
- WORD( para ) = EN_P+1 ;
- p = para+2;
- for( t=0 ; t<= 256 ; t+=step,p+=4 )
- {
- x = (r * cos256( t ) );
- y = (r * sin256( t ) * rby + 0x80 >>8 ); /* 四捨五入 */
-
- WORD( p ) = ox + ((x*rcos - y*rsin) >>16) ;
- WORD( p+2 ) = oy + ((x*rsin + y*rcos) >>16) ;
- }
-
- EGB_connect( EgbPtr, para );
-
- PI_FREE( para );
-
- return NOERR;
- }
-
- /*************************************/
-
- int APL_exec()
- {
- int mode,pen,ret;
-
- mode = cnfg[0].val;
- pen = cnfg[1].val;
-
- if( get_Points() ) return ERROR;
-
- EGB_writePage( EgbPtr, PI_PAGE );
- EGB_writeMode( EgbPtr, EGB_PSET );
-
- /* タイル指定を有効に */
- if( PI_TILEFLG )
- { EGB_tilePattern( EgbPtr, EGB_FORECOL,
- PI_TILE_X, PI_TILE_Y, PI_TILE_PAT );
- EGB_paintMode( EgbPtr, EGB_PAINT_TILE );
- }else
- { EGB_color( EgbPtr, EGB_FORECOL, PI_FORECOL );
- EGB_paintMode( EgbPtr, EGB_PAINT_BETA );
- }
- EGB_penSize( EgbPtr, pen );
-
-
- if( mode==0 ) return circle_slant();
- else if( mode==1 ) return circle_3Points();
- else return ERROR;
-
- }
-
-